﻿//////////////////////////////////////////////////////////////////////////////
//
//  Copyright © 1998-2024 Glodon Company Limited.  All rights reserved.
//
//  Use of this software is subject to the terms of the Glodon license
//  agreement provided at the time of installation or download, or which
//  otherwise accompanies this software in either electronic or hard copy form.  
//
//////////////////////////////////////////////////////////////////////////////

#pragma once
#include "NdbDataSchema.h"

///////////////////////////////////////////////////////////
//关联更新宏
#define REGISTER_REGEN_DATA_ID(CLASS_NAME, NAME)  \
    int Get##CLASS_NAME##NAME##RegenDataName(const std::wstring & ndbClassName) {static int name = gcmp::IRegeneratorDataIdCreator::CreateRegenDataId(WSTRING_OF(NAME), ndbClassName); return name;} \

//关联更新相关的数据，需声明关联更新相关方法
//NAME与DATA宏定义的相应数据名称一致
#define DECLARE_REGEN_FUNCTIONS(NAME)  \
    public:  RegenDataId Get##NAME##RdId() const; \
    public:  void Mark##NAME##RdId();  \
    private:  void ValidateRegenData##NAME##Use() const;  \

//关联更新相关的数据，需声明关联更新相关方法(方法为override时使用)
//NAME与DATA宏定义的相应数据名称一致
#define DECLARE_OVERRIDE_REGEN_FUNCTIONS(NAME)  \
    public:  RegenDataId Get##NAME##RdId() const override; \
    public:  void Mark##NAME##RdId() override; \
    private:  void ValidateRegenData##NAME##Use() const;  \

//关联更新相关的数据，需声明关联更新相关方法(方法为仅override Get##NAME##RdId时使用)
//NAME与DATA宏定义的相应数据名称一致
#define DECLARE_GETRDID_OVERRIDE_REGEN_FUNCTIONS(NAME)  \
    public:  RegenDataId Get##NAME##RdId() const override; \
    public:  void Mark##NAME##RdId(); \
    private:  void ValidateRegenData##NAME##Use() const;  \

//关联更新相关的数据，需实现关联更新相关方法
#define IMPLEMENT_REGEN_FUNCTIONS(NAMESPACE, CLASS_NAME, NAME)  \
    IMPLEMENT_REGEN_FUNCTIONS_EXT(NAMESPACE, CLASS_NAME, NAME, -1)

//关联更新相关的数据，需实现关联更新相关方法
#define IMPLEMENT_REGEN_FUNCTIONS_MULTIPLE_CALCULATORS(NAMESPACE, CLASS_NAME, NAME)  \
    IMPLEMENT_REGEN_FUNCTIONS_EXT(NAMESPACE, CLASS_NAME, NAME, MULTIPLE_CALCULATOR_EXTENDEDID)

//关联更新相关的数据，需实现关联更新相关方法
#define IMPLEMENT_REGEN_FUNCTIONS_EXT(NAMESPACE, CLASS_NAME, NAME, EXTENDED_ID)  \
    REGISTER_REGEN_DATA_ID(CLASS_NAME, NAME) \
    RegenDataId NAMESPACE::CLASS_NAME::Get##NAME##RdId() const{static std::wstring sNdbClassName = WSTRING_OF(CLASS_NAME); return RegenDataId(GetOwnerElementId().AsInt64(), Get##CLASS_NAME##NAME##RegenDataName(sNdbClassName), EXTENDED_ID);}  \
    void NAMESPACE::CLASS_NAME::Mark##NAME##RdId()  \
    {                                               \
        if (!GetDocument()) return;                 \
        GetDocument()->GetRegenerator()->MarkRegenDataId(Get##NAME##RdId()); \
    }                                               \
    void NAMESPACE::CLASS_NAME::ValidateRegenData##NAME##Use() const  \
    {                                               \
        if (!GetDocument())  return;                \
            GetDocument()->GetRegenerator()->ValidateRegenDataUse(Get##NAME##RdId()); \
    }
///////////////////////////////////////////////////////////
//关联更新数据定义宏
#define DATA_REGEN(TYPE, NAME)  \
    DATA_REGEN_CUSTOM(TYPE, NAME, gcmp::PBT_SupportAll)

#define DATA_REGEN_OVERRIDE(TYPE, NAME)  \
    DATA_REGEN_CUSTOM_OVERRIDE(TYPE, NAME, gcmp::PBT_SupportAll)

#define DATA_TRANSIENT_REGEN(TYPE, NAME)  \
    DATA_REGEN_CUSTOM(TYPE, NAME, gcmp::PBT_Transient)

#define DATA_TRANSIENT_REGEN_OVERRIDE(TYPE, NAME)  \
    DATA_REGEN_CUSTOM_OVERRIDE(TYPE, NAME, gcmp::PBT_Transient)

#define ENUM_DATA_REGEN(TYPE, NAME)  \
    ENUM_DATA_REGEN_CUSTOM(TYPE, NAME, gcmp::PBT_SupportAll)

#define ARR_DATA_REGEN(TYPE, NAME)  \
    ARR_DATA_REGEN_CUSTOM(TYPE, NAME, gcmp::PBT_SupportAll)

#define MAP_DATA_REGEN(KEY_TYPE, VALUE_TYPE, NAME, BEHAVIOUR_TYPES)  \
    MAP_DATA_REGEN_CUSTOM(KEY_TYPE, VALUE_TYPE, NAME, gcmp::PBT_SupportAll)  

#define UMAP_DATA_REGEN(KEY_TYPE, VALUE_TYPE, HASH_FUNC, NAME)  \
    UMAP_DATA_REGEN_CUSTOM(KEY_TYPE, VALUE_TYPE, HASH_FUNC, NAME, gcmp::PBT_SupportAll) 
